﻿using UnityEngine;

// 箱子
public class Box: BaseGameObject {
    protected Sprite mImage2;           // 图片2
    private int mLayerMask = 0;         // 层掩码
    protected SpriteRenderer mRenderer; // 图片渲染器

    /**
     * 移动。
     * @param direction     方向
     * @param moveResult    移动结果
     * @return 被推动的物体
     */
    public override BaseGameObject Move(KeyCode direction, ref MoveResult moveResult) {
        Vector2 origin = Vector2.zero;                                      // 射线起点
        RaycastHit2D raycastHit2D = new RaycastHit2D();                     // 射线碰撞信息
        bool leftFromDest = false;                                          // 是否离开目的地
        float destX = transform.position.x, destY = transform.position.y;   // 新位置的坐标

        // 检查新位置上是否有物体并计算新位置
        if (direction == KeyCode.LeftArrow) {
            origin = new Vector2(transform.position.x - Game.Pivot.x - Const.RAY_LENGTH, transform.position.y);
            raycastHit2D = Physics2D.Raycast(origin, Vector2.left, Const.RAY_LENGTH);
            destX--;
        } else if (direction == KeyCode.RightArrow) {
            origin = new Vector2(transform.position.x + Game.Pivot.x + Const.RAY_LENGTH, transform.position.y);
            raycastHit2D = Physics2D.Raycast(origin, Vector2.right, Const.RAY_LENGTH);
            destX++;
        } else if (direction == KeyCode.UpArrow) {
            origin = new Vector2(transform.position.x, transform.position.y + Game.Pivot.y + Const.RAY_LENGTH);
            raycastHit2D = Physics2D.Raycast(origin, Vector2.up, Const.RAY_LENGTH);
            destY++;
        } else if (direction == KeyCode.DownArrow) {
            origin = new Vector2(transform.position.x, transform.position.y - Game.Pivot.y - Const.RAY_LENGTH);
            raycastHit2D = Physics2D.Raycast(origin, Vector2.down, Const.RAY_LENGTH);
            destY--;
        }

        // 如果旁边是墙或箱子，则直接返回
        BaseGameObject neighbor;
        if (raycastHit2D.collider != null) {
            neighbor = base.Get(raycastHit2D.collider.gameObject);
            if (neighbor.type == Type.WALL || neighbor.type == Type.BOX) {
                moveResult = MoveResult.NO_MOVE;
                return null;
            }
        }

        // 设置移动结果
        if (moveResult < MoveResult.NORMAL_MOVED) {
            moveResult = MoveResult.NORMAL_MOVED;
        }

        // 判断是否要离开目的地
        raycastHit2D = Physics2D.Raycast(transform.position, Vector2.zero, Const.RAY_LENGTH, mLayerMask);
        if (raycastHit2D.transform != null) {
            BaseGameObject back = Get(raycastHit2D.transform.gameObject);
            if (type == Type.BOX && back?.type == Type.DESTINATION) {
                leftFromDest = true;
                moveResult = MoveResult.LEFT_FROM_DEST;
                mRenderer.sprite = mImage;
            }
        }

        // 移动
        transform.position = new Vector3(destX, destY, -1);

        // 判断是否到达目的地
        raycastHit2D = Physics2D.Raycast(transform.position, Vector2.zero, Const.RAY_LENGTH, mLayerMask);
        if (raycastHit2D.transform != null) {
            BaseGameObject back = Get(raycastHit2D.transform.gameObject);
            if (type == Type.BOX && back?.type == Type.DESTINATION) {
                if (leftFromDest) {
                    moveResult = MoveResult.NORMAL_MOVED;
                } else {
                    moveResult = MoveResult.ARRIVED_ON_DEST;
                }
                mRenderer.sprite = mImage2;
            }
        }

        return this;
    }

    /**
     * 开始。
     */
    protected new void Start() {
        base.Start();

        // 初始化成员
        string imageFilePath = string.Format(Const.IMAGE_FILE_PATH, (int)type * 10 + 1);
        mImage2 = Resources.Load<Sprite>(imageFilePath);
        mLayerMask = LayerMask.GetMask(Const.LAYER_DESTINATION);
        mRenderer = gameObject.GetComponent<SpriteRenderer>();
    }
}
